package com.wzy.oa_sys.service.impl.attendance;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.wzy.oa_sys.mapper.attendance.VacationMapper;
import com.wzy.oa_sys.mapper.user.UserMapper;
import com.wzy.oa_sys.model.pojo.attendance.OaVacation;
import com.wzy.oa_sys.model.pojo.user.OaUser;
import com.wzy.oa_sys.model.request.attendance.VacationReq;
import com.wzy.oa_sys.model.request.notice.NoticeReq;
import com.wzy.oa_sys.model.response.attendance.VacationResp;
import com.wzy.oa_sys.service.attendance.VacationService;
import com.wzy.oa_sys.service.notice.NoticeService;
import com.wzy.oa_sys.util.JwtUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.sql.Time;
import java.time.LocalDateTime;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class VacationServiceImpl extends ServiceImpl<VacationMapper, OaVacation> implements VacationService {


    @Autowired
    private VacationMapper vacationMapper;
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private NoticeService noticeService;
    @Autowired
    private JwtUtil jwtUtil;

    @Override
    public List<VacationResp> getVacationList() {
        List<OaVacation> vacationList = vacationMapper.selectList(null);
        vacationList.sort(Comparator.comparing(OaVacation::getNState));
        List<VacationResp> vacationRespList = new ArrayList<>();
        vacationList.forEach(vacation -> {
            if(vacation.getCExamine().equals("0")){
                VacationResp build = VacationResp.builder()
                        .id(vacation.getNVacationId())
                        .name(userMapper.selectUserById(vacation.getNUserId()).getCRealName())
                        .userId(vacation.getNUserId())
                        .type(vacation.getCType())
                        .starttime(vacation.getDtStartTime())
                        .deadline(vacation.getDtDeadline())
                        .reason(vacation.getCReason())
                        .time(vacation.getDtTime())
                        .reviewId(vacation.getCReviewerId())
                        .exreason(vacation.getCReason())
                        .examine("待审核")
                        .build();
                if(vacation.getNState()==1){
                    build.setState("紧急");
                }else if(vacation.getNState()==2){
                    build.setState("重要");
                }else if(vacation.getNState()==3){
                    build.setState("正常");
                }
                if(userMapper.selectUserById(vacation.getCReviewerId())!=null){
                    build.setReviewer(userMapper.selectUserById(vacation.getCReviewerId()).getCRealName());
                }
                vacationRespList.add(build);
            }

        });
        return vacationRespList;
    }

    //超管理员看所有，普管看自己部门下，普通用户看自己
    //加编辑功能
    @Override
    public List<VacationResp> getApprovedVacationList(HttpServletRequest request) {
        String role = jwtUtil.extractUserRole(request);
        Long userId = jwtUtil.extractUserId(request);
        List<OaVacation> vacationList = vacationMapper.selectList(null);
        vacationList.sort(Comparator.comparing(OaVacation::getNState));
        List<VacationResp> vacationRespList = new ArrayList<>();
        vacationList.forEach(vacation -> {
            if(!vacation.getCExamine().equals("0")){
                VacationResp build = VacationResp.builder()
                        .id(vacation.getNVacationId())
                        .name(userMapper.selectUserById(vacation.getNUserId()).getCRealName())
                        .userId(vacation.getNUserId())
                        .type(vacation.getCType())
                        .starttime(vacation.getDtStartTime())
                        .deadline(vacation.getDtDeadline())
                        .reason(vacation.getCReason())
                        .exreason(vacation.getCReason())
                        .time(vacation.getDtTime())
                        .reviewId(vacation.getCReviewerId())
                        .build();
                if(vacation.getCExamine().equals("1")){
                    build.setExamine("审核通过");
                }else if(vacation.getCExamine().equals("2")){
                    build.setExamine("审核未通过");
                }
                if(vacation.getNState()==1){
                    build.setState("紧急");
                }else if(vacation.getNState()==2){
                    build.setState("重要");
                }else if(vacation.getNState()==3){
                    build.setState("正常");
                }
                if(userMapper.selectUserById(vacation.getCReviewerId())!=null){
                    build.setReviewer(userMapper.selectUserById(vacation.getCReviewerId()).getCRealName());
                }
                vacationRespList.add(build);
            }

        });
        if(role.contains("SUPERMAN")){
            return vacationRespList;
        }else if(role.contains("MANAGER")){
            QueryWrapper<OaUser> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("n_user_id", userId);
            List<VacationResp> vacationRespList1 = new ArrayList<>();
            if(userMapper.selectOne(queryWrapper)!=null){
                long nDeptId = userMapper.selectOne(queryWrapper).getNDeptId();
                QueryWrapper<OaUser> queryWrapper2 = new QueryWrapper<>();
                queryWrapper2.eq("n_dept_id", nDeptId);
                if(userMapper.selectList(queryWrapper2)!=null){
                    List<OaUser> oaUsers = userMapper.selectList(queryWrapper2);
                    HashSet<Long> userIds = new HashSet<>();
                    for (OaUser oaUser : oaUsers) {
                        userIds.add(oaUser.getNUserId());
                    }
                    vacationRespList.forEach(oaVacation -> {
                        if(userIds.contains(oaVacation.getUserId())){
                            vacationRespList1.add(oaVacation);
                        }
                    });
                }
            }
            return vacationRespList1;
        }else{
            List<VacationResp> collect = vacationRespList.stream().filter(oa -> oa.getUserId() == jwtUtil.extractUserId(request)).collect(Collectors.toList());
            return collect;
        }

    }

    @Override
    public void addVacation(VacationReq vacationReq,long userId) {
        OaVacation oaVacation = new OaVacation();
        oaVacation.setNUserId(userId);
        oaVacation.setCType(vacationReq.getType());
        LocalDateTime starttime = vacationReq.getStarttime();
        oaVacation.setDtStartTime(starttime.plusHours(8));
        LocalDateTime deadline = vacationReq.getDeadline();
        oaVacation.setDtDeadline(deadline.plusHours(8));
        oaVacation.setCReason(vacationReq.getReason());
        oaVacation.setNState(vacationReq.getState());
        oaVacation.setCExamine(vacationReq.getExamine());
        oaVacation.setDtTime(LocalDateTime.now());
        oaVacation.setCReviewerId(vacationReq.getReviewer());
        vacationMapper.insert(oaVacation);
    }


    //审核通过的请假信息不支持修改
    @Override
    public void updateVacation(VacationReq vacationReq, HttpServletRequest request) {
        Long userId = jwtUtil.extractUserId(request);
        //找到对应的请假信息
        QueryWrapper<OaVacation> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("n_vacation_id", vacationReq.getId());
        OaVacation oaVacation = vacationMapper.selectOne(queryWrapper);
        boolean flag = false;
        //找到就进行更新
        if(oaVacation!=null){
            if(!vacationReq.getType().equals(oaVacation.getCType())){
                flag = true;
                oaVacation.setCType(vacationReq.getType());
            }
            if(!vacationReq.getStarttime().equals(oaVacation.getDtStartTime())){
                flag = true;
                LocalDateTime starttime = vacationReq.getStarttime();
                oaVacation.setDtStartTime(starttime);
            }
            if(!vacationReq.getDeadline().equals(oaVacation.getDtDeadline())){
                flag = true;
                LocalDateTime deadline = vacationReq.getDeadline();
                oaVacation.setDtDeadline(deadline);
            }
            if(!oaVacation.getCReason().equals(vacationReq.getReason())){
                flag = true;
                oaVacation.setCReason(vacationReq.getReason());
            }
            if(oaVacation.getNState()!=vacationReq.getState()){
                flag = true;
                oaVacation.setNState(vacationReq.getState());
            }
            if(flag){
                if(vacationReq.getExamine().equals("待审核")){
                    oaVacation.setCExamine("0");
                }else if(vacationReq.getExamine().equals("审核未通过")){
                    oaVacation.setCExamine("0");
                }else if(vacationReq.getExamine().equals("审核通过")){
                    oaVacation.setCExamine("1");
                }
                oaVacation.setDtTime(LocalDateTime.now());
                vacationMapper.update(oaVacation,queryWrapper);
            }else{
                System.out.println("未修改===================");
                throw new RuntimeException("请假信息未修改");
            }

        }
    }

    @Override
    public int deleteVacationById(Integer id) {
        return vacationMapper.deleteVacationById(id);
    }

    @Override
    public VacationResp getVacationDetailById(Integer id) {
        QueryWrapper<OaVacation> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("n_vacation_id", id);
        OaVacation oaVacation = vacationMapper.selectOne(queryWrapper);
        if(oaVacation!=null){
            VacationResp build = VacationResp.builder()
                    .id(oaVacation.getNVacationId())
                    .userId(oaVacation.getNUserId())
                    .type(oaVacation.getCType())
                    .starttime(oaVacation.getDtStartTime())
                    .deadline(oaVacation.getDtDeadline())
                    .reason(oaVacation.getCReason())
                    .time(oaVacation.getDtTime())
                    .exreason(oaVacation.getCExReason()).build();

            if(oaVacation.getNState() == 3){
                build.setState("正常");
            }else if(oaVacation.getNState() == 2){
                build.setState("重要");
            }else if(oaVacation.getNState() == 1){
                build.setState("紧急");
            }
            if(build.getExreason()==null||build.getExreason().equals("")){
                build.setExreason("无原因");
            }
            if(oaVacation.getNUserId() != 0){
                if(userMapper.selectUserById(oaVacation.getNUserId())!=null){
                build.setName(userMapper.selectUserById(oaVacation.getNUserId()).getCRealName());
                }
            }
            if(oaVacation.getCReviewerId() != 0){
                if(userMapper.selectUserById(oaVacation.getCReviewerId())!=null){
                    build.setReviewer(userMapper.selectUserById(oaVacation.getCReviewerId()).getCRealName());
                }
            }
            if(oaVacation.getCExamine().equals("0")){
                build.setExamine("待审核");
            }else if(oaVacation.getCExamine().equals("1")){
                build.setExamine("通过");
            }else if(oaVacation.getCExamine().equals("2")){
                build.setExamine("不通过");
            }
            return build;
        }
        return null;
    }

    @Override
    public List<VacationResp> getICanApprovedVacations(long userId) {
        QueryWrapper<OaUser> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("n_user_id", userId);
        OaUser oaUser = userMapper.selectOne(queryWrapper);

        List<VacationResp> vacationRespList = getVacationList();

        // 判断角色并进行相应的过滤
        if (oaUser.getNRole() == 1) {
            return vacationRespList; // 角色为1，返回全部请假列表
        } else if (oaUser.getNRole() == 2) {
            // 角色为2，仅保留 reviewId 等于 userId 的数据
            return vacationRespList.stream()
                    .filter(vacation -> vacation.getReviewId() == userId) // 过滤
                    .collect(Collectors.toList()); // 收集结果为列表
        }

        return vacationRespList; // 默认返回（可能是为了编译的安全）
    }

    @Override
    public void updateTheVacation(VacationReq vacationReq, HttpServletRequest request) {
        Long userId = jwtUtil.extractUserId(request);
        QueryWrapper<OaVacation> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("n_vacation_id", vacationReq.getId());
        OaVacation oaVacation = vacationMapper.selectOne(queryWrapper);
        if(oaVacation!=null){
            oaVacation.setCExamine(vacationReq.getExamine());
            oaVacation.setCExReason(vacationReq.getExreason());
            //请假审核后发布通知
            NoticeReq noticeReq = new NoticeReq();
            noticeReq.setType("更新");
            noticeReq.setState(2);
            noticeReq.setTitle("请假审核结果通知");
            noticeReq.setDesc("您有一条请假审核结果通知，请注意查看。可点击链接查看具体信息。");
            noticeReq.setReleasetime(LocalDateTime.now().minusHours(8));
            //请假人信息
            OaUser oaUser = userMapper.selectUserById(oaVacation.getNUserId());
            noticeReq.setDeptname(oaUser.getNDeptId());
            ArrayList<Long> cRecipient = new ArrayList<>();
            cRecipient.add(oaUser.getNUserId());
            noticeReq.setReceiverList(cRecipient);
            noticeReq.setReviewer(userId);
            noticeReq.setExamine("1");
            noticeReq.setExReason("请假信息审核消息");
            noticeReq.setLinkId(vacationReq.getId());
            noticeReq.setLinkType("vacation");
            noticeService.addNotice(noticeReq,userId);
            vacationMapper.updateVacationById(oaVacation);
        }else{
            System.out.println("不存在该请假记录");
        }
    }

    //查看我可查看的请假信息
    //管理员查看所有，普通管理员查看本部门，普通用户查看自己
    @Override
    public List<VacationResp> getICanSeeVacations(HttpServletRequest request) {
        String role = jwtUtil.extractUserRole(request);
        List<VacationResp> vacationList = getVacationList();
        List<VacationResp> vacationRespList = new ArrayList<>();
        if(role.contains("SUPERMAN")){
            return vacationList;
        }else if(role.contains("MANAGER")){
            QueryWrapper<OaUser> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("n_user_id", jwtUtil.extractUserId(request));
            if(userMapper.selectOne(queryWrapper)!=null){
                long nDeptId = userMapper.selectOne(queryWrapper).getNDeptId();
                QueryWrapper<OaUser> queryWrapper2 = new QueryWrapper<>();
                queryWrapper2.eq("n_dept_id", nDeptId);
                if(userMapper.selectList(queryWrapper2)!=null){
                    List<OaUser> oaUsers = userMapper.selectList(queryWrapper2);
                    HashSet<Long> userIds = new HashSet<>();
                    for (OaUser oaUser : oaUsers) {
                        userIds.add(oaUser.getNUserId());
                    }
                    vacationList.forEach(oaVacation -> {
                        if(userIds.contains(oaVacation.getUserId())){
                            vacationRespList.add(oaVacation);
                        }
                    });
                }
            }
            return vacationRespList;
        }else{
            List<VacationResp> collect = vacationList.stream().filter(oa -> oa.getUserId() == jwtUtil.extractUserId(request)).collect(Collectors.toList());
            return collect;
        }
    }
}
